using System;
using System.Runtime.InteropServices;
using System.Threading;
using Oracle.ManagedDataAccess.Client;
using Oracle.ManagedDataAccess.Types;
using OracleInternal.Common;
using OracleInternal.MTS;

namespace OracleInternal.ConnectionPool
{
	[StructLayout(LayoutKind.Sequential)]
	internal class PoolResource<PM, CP, PR> : IOraclePoolResource where PM : PoolManager<PM, CP, PR>, new()where CP : Pool<PM, CP, PR>, new()where PR : PoolResource<PM, CP, PR>, new()
	{
		public DateTime m_creationTime;

		public string m_databaseDomainName;

		public string m_instanceName;

		public string m_databaseName;

		public string m_hostName;

		public PM m_pm;

		public CP m_cp;

		public DeletionRequestor m_deletionRequestor;

		public ConnectionString m_cs;

		public ManualResetEventSlim m_eventConCreated;

		public ManualResetEventSlim m_eventConTimeout;

		public bool m_bTimedOut;

		public int m_conTimeout;

		public Exception m_exception;

		public string m_id;

		public DateTime m_lastCheckOutTime;

		public bool m_bEndUserSessionEstablished;

		public int m_endUserSessionId = -1;

		internal int m_endUserSerialNum = -1;

		public int m_pxyUserSessionId = -1;

		internal int m_pxyUserSerialNum = -1;

		internal bool m_bPutCompleted;

		internal bool m_bCheckedOutByApp;

		internal bool m_bCheckedOutByDTC;

		internal bool m_bClosedWithReplacement;

		internal bool m_bDynamicallyEnlisted;

		internal MTSTxnCtx m_mtsTxnCtx;

		internal TransactionContext<PM, CP, PR> m_txnCtx;

		internal SessionType m_sessionType;

		internal int m_dbMajorVersion;

		internal int m_dbMinorVersion;

		internal int m_dbPatchsetVersion;

		internal string m_localTxnId;

		internal string m_affinityInstance;

		internal OracleIntervalDS m_sessionTimeZone;

		internal int m_resPoolRefCount;

		internal bool m_bTxnCtxPrimaryCon;

		internal bool m_isDb10gR2OrHigher;

		internal bool m_isDb11gR1OrHigher;

		internal bool m_isDb12cR1OrHigher;

		internal string m_connectionClass;

		internal bool bGotMatchingServerProcess;

		internal bool bDRCPServerProcessAttached;

		internal uint[] m_criteriaIds;

		internal bool bSessionSwitched;

		internal bool m_bCheckIfAlterSessionReqd = true;

		internal string m_preFailoverInstName;

		internal bool m_failoverOccured;

		internal int requestingThreadId;

		public bool m_bReconnectAtNullState;

		internal virtual string ServiceName => null;

		internal virtual string PdbName => null;

		internal virtual string EditionName => null;

		public PoolResource()
		{
			m_id = GetHashCode().ToString();
			m_criteriaIds = new uint[3];
			m_criteriaIds[0] = 0u;
			m_criteriaIds[1] = 0u;
		}

		public virtual void Connect(ConnectionString cs, bool bForPoolPopulation, OracleConnection connRefForCriteria, string instanceName = null)
		{
		}

		public virtual void AttachServerProcess(long sessionFlags, bool bUseDRCPMultiTag, ref long s2cSessionFlags)
		{
		}

		public virtual void DetachServerProcess(string drcpTagName, bool bUseDRCPMultiTag)
		{
		}

		internal virtual void BeginRequest()
		{
		}

		internal virtual void EndRequest()
		{
		}

		public virtual void DisConnect(OracleConnection connRefForCriteria)
		{
		}

		public virtual bool Dump()
		{
			return true;
		}

		internal virtual bool PingServer()
		{
			return true;
		}

		internal virtual bool IsTAFEnabled()
		{
			return false;
		}

		internal virtual bool TransportAlive()
		{
			return true;
		}

		internal virtual void GetAttributes()
		{
		}

		internal virtual void UpdateAttributes()
		{
		}

		internal virtual void GetConStrDefaults()
		{
		}

		internal virtual string GetDefaultEditionName()
		{
			return null;
		}

		internal virtual bool[] ProcessCriteriaCtx(OracleConnection connRefForCriteria)
		{
			if (ProviderConfig.m_bTraceLevelPrivate)
			{
				Trace.Write(OracleTraceLevel.Private, OracleTraceTag.Entry, OracleTraceClassName.PoolResource, OracleTraceFuncName.ProcessCriteriaCtx);
			}
			try
			{
				if (!m_isDb12cR1OrHigher && !string.IsNullOrEmpty(connRefForCriteria.m_criteriaPdbName))
				{
					throw new OracleException(-7500, string.Empty, string.Empty, OracleStringResourceManager.GetErrorMesg(-7500, "12c", "Multitenant"));
				}
				if (!m_isDb11gR1OrHigher && !string.IsNullOrEmpty(connRefForCriteria.m_criteriaEdition))
				{
					throw new OracleException(-7500, string.Empty, string.Empty, OracleStringResourceManager.GetErrorMesg(-7500, "11g", "Edition Based Redefinition"));
				}
				bool[] result = null;
				if (connRefForCriteria != null && !connRefForCriteria.m_bCriteriaPrelimAuthSession)
				{
					bool flag = false;
					bool flag2 = false;
					if (string.IsNullOrEmpty(connRefForCriteria.m_criteriaPdbName) && m_pm != null)
					{
						connRefForCriteria.m_criteriaPdbName = m_pm.m_conStrPdbName;
						connRefForCriteria.m_criteriaServiceName = m_pm.m_conStrServiceName;
					}
					if (string.IsNullOrEmpty(connRefForCriteria.m_criteriaPdbName))
					{
						flag = true;
					}
					if (connRefForCriteria.m_criteriaPdbName != null && GetPdbNameFromDb() != null && connRefForCriteria.m_criteriaPdbName.Equals(GetPdbNameFromDb(), StringComparison.InvariantCultureIgnoreCase) && (string.IsNullOrEmpty(connRefForCriteria.m_criteriaServiceName) || connRefForCriteria.m_criteriaServiceName.Equals(ServiceName, StringComparison.InvariantCultureIgnoreCase)))
					{
						flag = true;
					}
					if (!m_isDb11gR1OrHigher)
					{
						flag2 = true;
					}
					else
					{
						string text = EditionName;
						string text2 = null;
						if (!string.IsNullOrEmpty(connRefForCriteria.m_criteriaEdition))
						{
							if (connRefForCriteria.m_criteriaEdition[0] == '"')
							{
								int num = connRefForCriteria.m_criteriaEdition.IndexOf('"', 1);
								text2 = connRefForCriteria.m_criteriaEdition.Substring(1, num - 1);
							}
							else
							{
								text2 = connRefForCriteria.m_criteriaEdition.ToUpper();
							}
						}
						if (text2 == text)
						{
							flag2 = true;
						}
						else
						{
							if (text == null)
							{
								text = GetDefaultEditionName();
							}
							else if (text2 == null)
							{
								text2 = GetDefaultEditionName();
							}
							flag2 = ((text == text2) ? true : false);
						}
					}
					result = new bool[2]
					{
						!flag,
						!flag2
					};
				}
				return result;
			}
			catch (Exception ex)
			{
				OracleException.HandleError(OracleTraceLevel.Private, (OracleTraceTag)268697600, OracleTraceClassName.PoolResource, OracleTraceFuncName.ProcessCriteriaCtx, ex);
				throw new OracleException(-7505, string.Empty, string.Empty, OracleStringResourceManager.GetErrorMesg(-7505), ex);
			}
			finally
			{
				if (ProviderConfig.m_bTraceLevelPrivate)
				{
					Trace.Write(OracleTraceLevel.Private, (OracleTraceTag)262656, OracleTraceClassName.PoolResource, OracleTraceFuncName.ProcessCriteriaCtx);
				}
			}
		}

		internal virtual bool AlterSession(bool[] alterConnectionTuple, OracleConnection connRefForCriteria)
		{
			return false;
		}

		internal virtual string GetPdbNameFromDb()
		{
			string text = PdbName;
			if (string.IsNullOrEmpty(text))
			{
				GetConStrDefaults();
				text = m_pm.m_conStrPdbName;
			}
			return text;
		}
	}
}
